<?

namespace App\Servers\WebSocket\Logics;

use App\Servers\WebSocket\abstracts\LogicAbstract;
use App\Servers\WebSocket\Utils\JWT;

/**
 * JSON Web AccessToken
 */
class JwtManage extends LogicAbstract
{


    /**
     * 获取token
     *
     * @param [type] $data 包含`refreshToken`
     * @return array
     */
    public function token($data): array
    {
        if (isset($data->refreshToken) && JWT::isExpire($data->refreshToken)) {
            $payload = JWT::decode($data->refreshToken);
            $token = JWT::encode(['user_id' => $payload['user_id']]);   //jwt令牌
            return ['code' => 1, 'msg' => '刷新令牌成功', 'token' => $token];
        } else {
            return ['code' => 1000, 'msg' => '刷新令牌失败'];
        }
    }

    /**
     * 利用refreshToken进行自动登录
     *
     * @param [type] $data
     * @return array
     */
    public function login($data): array
    {
        if (!$data || !isset($data->refreshToken)) {
            return ['code' => 1000, 'msg' => '令牌登录失败','data'=>$data];
        }
        
        $payload = JWT::decode($data->refreshToken);
        if ($payload === null) {
            return ['code' => 1000, 'msg' => '令牌登录失败'];
        }
        $pdo = $this->threadTool['pdo']->get();
        // 准备预处理语句
        $stmt = $pdo->prepare("SELECT id,password_hash,username,nickname,email,phone,gender,birthday,avatar,register_time,register_ip,last_login_time,last_login_ip FROM users WHERE id=:id");

        // 绑定参数并执行
        $stmt->execute([':id' => $payload['user_id']]);
        $user = $stmt->fetch(\PDO::FETCH_ASSOC);
        if ($user) {
            $token = JWT::encode(['user_id' => $user['id']]);   //jwt令牌
            unset($user['password_hash']);
            // 准备预处理语句
            $stmt = $pdo->prepare("UPDATE users SET refresh_token=:refresh_token, last_login_time=:last_login_time WHERE id=:user_id");
            // 绑定参数并执行
            $stmt->execute([':user_id' => $user['id'], ':refresh_token' => $data->refreshToken, 'last_login_time' => date('Y-m-d H:i:s')]);
            $rowCount = $stmt->rowCount();

            $this->threadTool['pdo']->put($pdo);
            return ['code' => 1, 'msg' => '令牌登录成功', 'token' => $token, 'refreshToken' => $data->refreshToken, "expiresIn" => $payload['exp'], 'userInfo' => $user];
        } else {
            $this->threadTool['pdo']->put($pdo);
            return ['code' => 1000, 'msg' => '令牌登录失败'];
        }
    }
}
